package com.ldy.core.util;


import java.io.IOException;
import java.util.ArrayList;
import java.util.List;
import java.util.Map;

import org.apache.commons.codec.Charsets;
import org.apache.http.HttpEntity;
import org.apache.http.HttpHost;
import org.apache.http.HttpResponse;
import org.apache.http.NameValuePair;
import org.apache.http.auth.AuthScope;
import org.apache.http.auth.UsernamePasswordCredentials;
import org.apache.http.client.ClientProtocolException;
import org.apache.http.client.CredentialsProvider;
import org.apache.http.client.config.CookieSpecs;
import org.apache.http.client.config.RequestConfig;
import org.apache.http.client.entity.UrlEncodedFormEntity;
import org.apache.http.client.methods.HttpGet;
import org.apache.http.client.methods.HttpPost;
import org.apache.http.client.utils.URIBuilder;
import org.apache.http.entity.StringEntity;
import org.apache.http.impl.client.BasicCredentialsProvider;
import org.apache.http.impl.client.CloseableHttpClient;
import org.apache.http.impl.client.HttpClientBuilder;
import org.apache.http.impl.client.HttpClients;
import org.apache.http.message.BasicNameValuePair;
import org.apache.http.util.EntityUtils;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.http.ResponseEntity;
import org.springframework.http.client.HttpComponentsClientHttpRequestFactory;
import org.springframework.web.client.RestTemplate;

import com.ldy.core.common.HttpResp;

public class HttpClientUtil {
    private static final Logger logger = LoggerFactory.getLogger(HttpClientUtil.class);

    // 发送GET请求
    public static HttpResp getRequest(String path, List<NameValuePair> parametersBody) throws Exception {
        URIBuilder uriBuilder = new URIBuilder(path);
        uriBuilder.setParameters(parametersBody);
        HttpGet get = new HttpGet(uriBuilder.build());
        CloseableHttpClient client = HttpClientBuilder.create().build();
        try {
            HttpResponse response = client.execute(get);
            int code = response.getStatusLine().getStatusCode();
            if (code >= 400) {
                logger.warn("Could not access  resource path: " + path + " Server returned http code: " + code);
            }
            return new HttpResp(EntityUtils.toString(response.getEntity()), code);
        } catch (ClientProtocolException e) {
            throw new Exception("postRequest -- Client protocol exception!", e);
        } catch (IOException e) {
            throw new Exception("postRequest -- IO error!", e);
        } finally {
            get.releaseConnection();
        }
    }
    public static void main(String[] args) {
        // 创建HttpClient并设置代理
        CloseableHttpClient httpClient = HttpClients.custom()
//            .setProxy(new HttpHost("代理服务器地址", 0))
            .build();
 
        // 创建HttpComponentsClientHttpRequestFactory实例
        HttpComponentsClientHttpRequestFactory requestFactory = new HttpComponentsClientHttpRequestFactory();
 
        // 将自定义的HttpClient设置到工厂中
        requestFactory.setHttpClient(httpClient);
 
        // 使用工厂创建RestTemplate实例
        RestTemplate restTemplate = new RestTemplate(requestFactory);
 
        // 之后你可以使用restTemplate来发送HTTP请求，它会通过代理服务器发送
        ResponseEntity<String> entity = restTemplate.getForEntity("http://ipinfo.io", String.class);
        System.out.println(entity.getBody());
    }
    

    // 发送GET请求
    public static String getRequest(String path, Map<String, String> header, String proxyIp, int port, String username, String pwd) throws Exception {
//        URIBuilder uriBuilder = new URIBuilder(path);
//        uriBuilder.setParameters(parametersBody);
        HttpGet get = new HttpGet(path);
        if (null != header) {
        	for (String key :header.keySet()) {
        		get.addHeader(key, header.get(key));
        	}
        }
        HttpClientBuilder build = HttpClients.custom();
        if (proxyIp != null) {        	
        	// 使用代理
        	CredentialsProvider credentialsProvider = new BasicCredentialsProvider();
        	credentialsProvider.setCredentials(AuthScope.ANY, new UsernamePasswordCredentials(username, pwd));
        	HttpHost proxy = new HttpHost(proxyIp, port, "http");
        	build.setProxy(proxy).setDefaultCredentialsProvider(credentialsProvider);
        }
        CloseableHttpClient client = build.build();

		RequestConfig defaultConfig = RequestConfig.custom().setCookieSpec(CookieSpecs.STANDARD).build();
		get.setConfig(defaultConfig);
        try {
            HttpResponse response = client.execute(get);
           
            int code = response.getStatusLine().getStatusCode();
            if (code >= 400) {
                logger.warn("Could not access  resource path: " + path + " Server returned http code: " + code);
            }
            return EntityUtils.toString(response.getEntity());
        } catch (ClientProtocolException e) {
            throw new Exception("postRequest -- Client protocol exception!", e);
        } catch (IOException e) {
            throw new Exception("postRequest -- IO error!", e);
        } finally {
            get.releaseConnection();
        }
    }

    // 发送POST请求（普通表单形式）
    public static String postForm(String path, List<NameValuePair> parametersBody) throws Exception {
        HttpEntity entity = new UrlEncodedFormEntity(parametersBody, Charsets.UTF_8);
        return postRequest(path, "application/x-www-form-urlencoded", entity);
    }
    
    // 发送POST请求（普通表单形式）
    public static String postForm(String path, Map<String, Object> map) throws Exception {
    	List<NameValuePair> parametersBody = new ArrayList<>();
    	for (String key: map.keySet()) {
    		parametersBody.add(new BasicNameValuePair(key, String.valueOf(map.get(key))));
    	}
    	HttpEntity entity = new UrlEncodedFormEntity(parametersBody, Charsets.UTF_8);
        return postRequest(path, "application/x-www-form-urlencoded", entity);
    }

    // 发送POST请求（JSON形式）
    public static String postJSON(String path, String json) throws Exception {
        StringEntity entity = new StringEntity(json, Charsets.UTF_8);
        return postRequest(path, "application/json", entity);
    }

    // 发送POST请求
    private static String postRequest(String path, String mediaType, HttpEntity entity) throws Exception {
        HttpPost post = new HttpPost(path);
        post.addHeader("Content-Type", mediaType);
        post.addHeader("Accept", "application/json");
        post.setEntity(entity);
        try {
            CloseableHttpClient client = HttpClientBuilder.create().build();
            HttpResponse response = client.execute(post);
            int code = response.getStatusLine().getStatusCode();
            if (code >= 400)
                throw new Exception(EntityUtils.toString(response.getEntity()));
            return EntityUtils.toString(response.getEntity());
        } catch (ClientProtocolException e) {
            throw new Exception("postRequest -- Client protocol exception!", e);
        } catch (IOException e) {
            throw new Exception("postRequest -- IO error!", e);
        } finally {
            post.releaseConnection();
		}
	}
}